import { WebSocketServer } from 'ws';
import http from 'http';
import fs from 'fs';
import path from 'path';

class PCMWebSocketServer {
    constructor(options = {}) {
        this.port = options.port || 8080;
        this.sampleRate = options.sampleRate || 8000;
        this.channels = options.channels || 1;
        this.bitDepth = options.bitDepth || 16;
        this.wss = null;
        this.httpServer = null;
        this.isPlaying = false;
        this.audioBuffer = [];
        this.outputDir = './temp_audio';
        this.index = 0;
        
        this.ensureOutputDir();
        this.initWebSocketServer();
    }

    ensureOutputDir() {
        if (!fs.existsSync(this.outputDir)) {
            fs.mkdirSync(this.outputDir, { recursive: true });
        }
    }

    initWebSocketServer() {
        this.httpServer = http.createServer((request, response) => {
            response.writeHead(200);
            response.end('PCM WebSocket Server');
        });

        this.wss = new WebSocketServer({ server: this.httpServer });

        this.wss.on('connection', (socket, request) => {
            const origin = request?.headers?.origin || '';
            if (origin) console.log('客户端请求连接:', origin);
            console.log('客户端已连接');

            socket.on('message', (data, isBinary) => {
                try {
                    this.handlePCMData(data, isBinary === true);
                } catch (error) {
                    console.error('处理消息时出错:', error.message);
                }
            });

            socket.on('close', (code, reason) => {
                const reasonText = Buffer.isBuffer(reason) ? reason.toString() : String(reason || '');
                console.log('客户端已断开连接, 代码:', code, '原因:', reasonText);
            });

            socket.on('error', (error) => {
                console.error('WebSocket连接错误:', error.message);
            });
        });

        this.httpServer.listen(this.port, () => {
            console.log(`WebSocket服务器已启动，监听端口 ${this.port}`);
        });
    }

    handlePCMData(data, isBinary) {
        this.index += 1;
        try {
            if (isBinary) {
                const buf = Buffer.isBuffer(data) ? data : Buffer.from(data);
                console.log(this.index,',收到二进制数据，长度:', buf.length);
                if (buf && buf.length > 0) this.playPCMData(buf);
            } else {
                const text = Buffer.isBuffer(data) ? data.toString() : String(data);
                console.log('收到文本消息:', text);
            }
        } catch (error) {
            console.error('处理PCM数据时出错:', error.message);
        }
    }

    playPCMData(pcmBuffer) {
        try {
            console.log(this.audioBuffer.length, ',保存PCM数据，长度:', pcmBuffer.length, '字节');
            
            if (pcmBuffer.length > 0) {
                this.audioBuffer.push(pcmBuffer);
                
                if (this.audioBuffer.length >= 500) {
                    this.saveAndPlayAudio();
                }
            }
        } catch (error) {
            console.error('处理PCM数据失败:', error);
        }
    }

    saveAndPlayAudio() {
        if (this.audioBuffer.length === 0) return;
        
        const combinedBuffer = Buffer.concat(this.audioBuffer);
        const timestamp = Date.now();
        const wavFilename = path.join(this.outputDir, `audio_${timestamp}.wav`);
        
        const wavBuffer = this.createWAVHeader(combinedBuffer);
        fs.writeFileSync(wavFilename, wavBuffer);
        console.log('WAV文件已保存:', wavFilename, '采样率:', this.sampleRate);
        
        this.audioBuffer = [];
    }

    createWAVHeader(pcmData) {
        const dataLength = pcmData.length;
        const fileLength = 36 + dataLength;
        
        const buffer = Buffer.alloc(44 + dataLength);
        
        // WAV文件头
        buffer.write('RIFF', 0);
        buffer.writeUInt32LE(fileLength, 4);
        buffer.write('WAVE', 8);
        buffer.write('fmt ', 12);
        buffer.writeUInt32LE(16, 16);
        buffer.writeUInt16LE(1, 20);
        buffer.writeUInt16LE(this.channels, 22);
        buffer.writeUInt32LE(this.sampleRate, 24);
        buffer.writeUInt32LE(this.sampleRate * this.channels * (this.bitDepth / 8), 28);
        buffer.writeUInt16LE(this.channels * (this.bitDepth / 8), 32);
        buffer.writeUInt16LE(this.bitDepth, 34);
        buffer.write('data', 36);
        buffer.writeUInt32LE(dataLength, 40);
        
        pcmData.copy(buffer, 44);
        
        return buffer;
    }

    start() {
        this.isPlaying = true;
        console.log('PCM播放服务器已启动');
    }

    stop() {
        this.isPlaying = false;
        if (this.wss) {
            this.wss.close();
        }
        if (this.httpServer) {
            this.httpServer.close();
        }
        if (this.audioBuffer.length > 0) {
            this.saveAndPlayAudio();
        }
        console.log('PCM播放服务器已停止');
    }
}

async function main() {
    const server = new PCMWebSocketServer({
        port: 4000,
        sampleRate: 8000,
        channels: 1,
        bitDepth: 16
    });

    server.start();
    
    process.on('SIGINT', () => {
        console.log('\n正在停止服务器...');
        server.stop();
        process.exit(0);
    });
}

main();
